package com.hk.service.order.impl;

import com.hk.commons.*;
import com.hk.commons.enm.MqEventType;
import com.hk.commons.entity.*;
import com.hk.commons.entity.order.OrderContract;
import com.hk.commons.entity.order.OrderInfo;
import com.hk.commons.entity.order.OrderRouteInfo;
import com.hk.commons.entity.product.ProductInfo;
import com.hk.commons.entity.sys.SysUser;
import com.hk.commons.utils.sys.DataHelper;
import com.hk.commons.utils.sys.DateHelper;
import com.hk.commons.vo.*;
import com.hk.dao.base.impl.BaseServiceImpl;
import com.hk.service.IOrganization;
import com.hk.service.IOrganization_New;
import com.hk.service.IPush;
import com.hk.service.IUserChannel;
import com.hk.service.kyc.ICoupon;
import com.hk.service.kyc.ILogUtil;
import com.hk.service.kyc.IUserCard;
import com.hk.service.mq.IMq;
import com.hk.service.order.*;
import com.hk.service.product.IProductInfo;
import com.hk.service.sys.IAnswer;
import com.hk.service.sys.ISysUser;
import com.hk.service.sys.ISysUserRoles;
import com.hk.service.sys.IUserCache;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.io.IOException;
import java.math.BigDecimal;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardOpenOption;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingQueue;

@Service
public class OrderInfoImpl extends BaseServiceImpl<OrderInfo> implements
		IOrderInfo {

	private static Long  FYJZH_PAYMENT_ID = Long.valueOf(ConstantPayment.FYJZH_PAY);
	@Autowired
	private IReservation reservationService;

	@Autowired
	private ISysUserRoles userRoleService;

	@Autowired
	private IOrderRouteInfo orderRouteService;

	@Autowired
	private ILogUtil logService;

	@Autowired
	private IUserCache userCacheService;

	@Autowired
	private OrderHandleContent orderContent;

	@Autowired
	private ISysUser userService;

	@Autowired
	private IContract contractService;

	@Autowired
	private IParameter parmService;

	@Value("${qingniu.pdf}")
	private String QN_PDF;

	@Value("${hk.logsBaseUrl}")
	private String logsBaseUrl;

	@Autowired
	private IProductInfo productService;

	@Autowired
	private ISysUserRoles roleService;

	@Autowired
	private IUserCard userCardService;

	@Autowired
	private IAnswer answerService;

	private Logger logger = LoggerFactory.getLogger(OrderInfoImpl.class);

	@Resource
	private JdbcTemplate jdbcTemplate;
	
	@Autowired
	ICoupon couponService;

	@Autowired
	private IPush pushService;

    @Autowired
    private IMq mqService;

	@Autowired
	private IOrderContract orderContractService;

	@Autowired
	private IOrganization orgService;

	@Autowired
	private IOrganization_New orgNewService;

	@Autowired
	private IUserChannel userChannelService;


	@Override
	public OrderInfo findById(long id) {

		return getById(id);
	}

	@Override
	public synchronized Long add(OrderInfo model) {
		logger.info("*********************** OrderInfoImpl add order start ****************");
		Long id = null;
		if (model.getId() == null) {
			id = LongId.get();
			model.setId(id);

			// 设置订单ID
			model.setOrderId(id.toString());
		} else {
			id = model.getId();
		}
		model.setOrderCreatedOn(System.currentTimeMillis());

		super.save(model);


		//新增订单，清除用户投资资产缓存
		try{
			userCacheService.removeUserAssetCache(model.getUserId());
		}catch (Exception e){
			logger.info("添加订单，删除用户投资资产缓存错误 error={}", e);
		}

		//调用多线程生成合同
		try {
			ExecutorService executor = Executors.newFixedThreadPool(1);
			Runnable task = new Runnable() {
				public void run() {

					contractService.create(model.getId());
					orderContractService.createByOrderId(model.getId());

					//更新订单的风险等级，并生成PDF版本的KYC
					createOrderKyc(model.getId());
				}
			};
			executor.execute(task);
			executor.shutdown();

		} catch (Exception e) {
			e.printStackTrace();
		}

		//判断是否派送家庭律师卡
		try {
			ExecutorService executor = Executors.newFixedThreadPool(1);
			Runnable task = new Runnable() {
				public void run() {
					try {
						Long seleepTime = Long.valueOf(1000 * 60 * 10);
						Thread.sleep(seleepTime);
						sendCard(model.getUserId());
					} catch (Exception e) {
						logger.info("after add order check secnd Card exception e={}", e);
					}
				}
			};
			executor.execute(task);
			executor.shutdown();

		} catch (Exception e) {
			e.printStackTrace();
		}



		//调用多线程生成提示信息
		try {
			ExecutorService executor = Executors.newFixedThreadPool(1);
			Runnable task = new Runnable() {
				public void run() {
					ProductInfo productInfo = productService.findById(model.getProductId());

					Parameter wyProd = parmService.getByName(ConstantParm.WY_PROD);

					String wyFlag = wyProd.getValue01();

					String prodFlag = productInfo.getProdFlag01();

					if(wyFlag.equals(prodFlag)){
						Boolean checkResult = productService.canBuy(model.getUserId()).getResult();
						logger.info("check can buy in the order save result = {}", checkResult);
						if(checkResult == true){
							logger.info("checkResult == true");
							RedisCilent.setString(model.getId().toString(), "恭喜您获得岁半增财（180天）和岁岁增盈（365天）收益额外增加0.2%的购买福利", 24 * 3600 * 1000);
						}

						logger.info("checkResult == false");

					}

					logger.info("非活动类产品");
				}
			};
			executor.execute(task);
			executor.shutdown();

		} catch (Exception e) {
			e.printStackTrace();
		}


        // 推送下单消息到活动中心
        try {
            ExecutorService executor = Executors.newFixedThreadPool(1);
            Runnable task = () -> {
                push(model);
            };
            executor.execute(task);
            executor.shutdown();
        } catch (Exception e) {
            logger.error("push mq msg to activity center error, ", e);
        }

		logger.info("*********************** OrderInfoImpl add order end **************** orderId ={}", id);
		return id;
	}

	private void push(OrderInfo orderInfo) {
        String dispatchEvent = MqEventType.USER_ORDER.toString();
        MqCenterMsg msg = MqCenterMsg.getMqCenterMsg(orderInfo.getUserId(), dispatchEvent);
        msg.setOrderId(orderInfo.getId());
        msg.setProductId(orderInfo.getProductId());
        msg.setOrderAmount(orderInfo.getSuccessAmount());
        mqService.setMessage(MqCenterMsg.CENTER_QUEUE_NAME, msg);
	}

	@Override
    public Boolean startDiv(Long productId, Timestamp tradeTime, Timestamp dividendDate) {

        logger.info("startDiv 产品起标 productId={}, tradeTime={}, dividendDate={}", productId, tradeTime, dividendDate);

        List<OrderInfo> orderList = getConfirmingOrderList(productId);

        if (orderList == null || orderList.size() <= 0)
            return false;

        logger.info("startDiv 产品起标 productId={}  orderList size ={}", productId, orderList.size());

        BlockingQueue<Long> orderContractQueue = new LinkedBlockingQueue<Long>();

        orderList.parallelStream()
                .map(order -> updateOrderDates(tradeTime, dividendDate, order))
                .forEach(orderId -> {
                    try {
                        orderContractQueue.put(orderId);
                    } catch (InterruptedException e) {
                        logger.error("startDiv productId={} order={} ContractQueue Error :", productId, orderId, e);
                    }
                });

        ExecutorService executor = Executors.newFixedThreadPool(1);
        Runnable task = () -> createContract(orderContractQueue);
        executor.execute(task);
        executor.shutdown();

        return true;
    }

    private void createContract(BlockingQueue<Long> orderContractQueue) {
        if (orderContractQueue == null || orderContractQueue.size() <= 0)
            return;

        //生成投资确认函
        try {
            while (orderContractQueue.size() > 0) {
                Long orderId = orderContractQueue.take();

                contractService.creatTZQRHPDF(orderId);
            }
        } catch (Exception e) {
            logger.error("Create Contract Error:", e);
        }

    }

    private List<OrderInfo> getConfirmingOrderList(Long productId) {
        HqlFilter hqlfilter = new HqlFilter();
        hqlfilter.addEQFilter("productId", productId);
        hqlfilter.addEQFilter("payStatus", ConstantOrderStatus.PAY_STATUS_TRUE);
        hqlfilter.addEQFilter("confirmStatus", ConstantOrderStatus.CONFIRM_STATUS__NO_CONFIRM);

        return findByFilter(hqlfilter);
    }

    private Long updateOrderDates(Timestamp tradeTime, Timestamp dividendDate, OrderInfo order) {
        order.setOrderConfirmDate(System.currentTimeMillis());
        order.setOrderTradeDate(tradeTime.getTime());
        order.setDividendDate(dividendDate.getTime());

        Long paymentId = order.getPaymentId();

		//起标划拨，清除用户投资资产缓存
		try{
			userCacheService.removeUserAssetCache(order.getUserId());
		}catch (Exception e){
			logger.info("起标划拨，删除用户投资资产缓存错误 error={}", e);
		}


        //如果不是金账户的订单，则直接改确认状态
        if (paymentId.equals(FYJZH_PAYMENT_ID)) {
            SysUser user = userService.findById(order.getUserId());

            //更改订单划拨状态为待划拨
            this.addTransferOrderIntoRedis(order.getId(), order.getContract_no(), user.getName(), order.getCreditorPhoneNum(), order.getSuccessAmount());

        } else {
            order.setConfirmStatus(ConstantOrderStatus.CONFIRM_STATUS__TRUE);
        }

        this.update(order);

        return order.getId();
    }


    /**
	 * 初始化订单信息
	 */
	@Override
	public OrderInfo initOrder(Long orderId, Long userId, Long productId,
			Long userCardId, BigDecimal amount) {

		logger.info("hk createOrderInfo create orderInfo orderId={}, userId={}, productId ={}, userCardId={}, amount={}",
				orderId, userId, productId, userCardId, amount);

		// 创建订单，用于保存在数据库
		OrderInfo orderInfo = new OrderInfo();
		
		ProductInfo prod = productService.findById(productId);
		SysUser user = userService.findById(userId);

		if (this.userRoleService.isTester(userId) == false) {
			if (prod.getIsTest().intValue() == 1) {
				return null;
			}
		}
		
		// 01 如果orderId 为空，则创建订单id
		if( orderId == null){
			orderId = LongIdThreadSafety.get();
		}
		
		orderInfo.setId(orderId);
				
				
		UserCardMsg userCardMsg = null;
		
		//获取卡券信息
		if(userCardId != null && (!userCardId.equals(Long.valueOf(0)))){

			userCardMsg = couponService.getCouponInfo(userId, userCardId);
			
			/*
			CheckInfo userCardCheckInfo = couponService.checkCoupon(userCardMsg, prod.getSaleType());
			
			
			if(userCardCheckInfo == null || userCardCheckInfo.getResult() == false){
				logger.info("hk createOrderInfo create order failed , userCard not active ");
				return null;	
			}
			*/
			
			// CheckInfo actUserCardcheckInfo = couponService.activeCoupon(userCardId, userId, orderId, true);
			//CheckInfo actUserCardcheckInfo = couponService.activeCoupon(userCardId, userId, orderId, true);

			// logger.info("hk createOrderInfo create order userCardActive result = {}", actUserCardcheckInfo.toString());
			//logger.info("hk createOrderInfo create order userCardActive result = {}", actUserCardcheckInfo.toString());

			/*
			//激活卡券，如果激活失败测退出
			if( actUserCardcheckInfo == null || actUserCardcheckInfo.getResult() == false){
				logger.info("hk createOrderInfo create order failed , userCard not active ");
				return null;	
			}
			*/
		}
		 
		// 02 创建订单，初始化订单的用户信息、理财师信息、所属渠道、所属部门、产品信息
		initOrderUserandProdInfo(orderInfo, user, prod);
		// 03 初始化订单时间相关的属性、订单创建时间、订单确认时间、订单起息日、订单还本付息日
		initOrderDateInfo(orderInfo, prod);
		// 04 初始化订单与钱相关的信息
		initOrderMoneyInfo(orderInfo, prod, userCardMsg, amount);
		// 05 设置产品的支付状态为未支付
		orderInfo.setPayStatus(ConstantOrderStatus.PAY_STATUS_FALSE);
		// 06 设置产品的确认状态为未确认
		orderInfo.setConfirmStatus(ConstantOrderStatus.CONFIRM_STATUS_FALSE);
		// 07 设置支付方式为富友金账户支付
		orderInfo.setPaymentId(Long.valueOf(ConstantPayment.FYJZH_PAY));
		//如果是金账户的订单，则直接设置为已支付、已确认
		if( prod.getSaleType() == ConstantProduct.PRODUCT_TEST_PRODUCT){
			//代金券或体验金setPayStatus
			orderInfo.setPayStatus(ConstantOrderStatus.PAY_STATUS_TRUE);  
			orderInfo.setConfirmStatus(ConstantOrderStatus.CONFIRM_STATUS__TRUE); 
		}
		logger.info("return orderInfo");
		
		return orderInfo;
	}

	private void initOrderUserandProdInfo(OrderInfo orderInfo,
			SysUser user, ProductInfo prod) {
		logger.info("hk createOrderInfo create orderInfo productId = "
				+ prod.getId() + "  userId = " + user.getId());

		int routeId = prod.getIssuerId();
		switch (routeId) {
		case ConstantRoute.COMPANY_HUAKANG:
			orderInfo.setBrokerOrderNo("hk" + orderInfo.getId().toString());
			break;
		case ConstantRoute.COMPANY_HUOCHAI:
			orderInfo.setBrokerOrderNo("hc" + orderInfo.getId().toString());
			break;
		case ConstantRoute.COMPANY_YINGMI:
			orderInfo.setBrokerOrderNo("ym" + orderInfo.getId().toString());
			break;
		default:
			orderInfo.setBrokerOrderNo("hk" + orderInfo.getId().toString());
		}

		// 01 添加用户属性

		orderInfo.setUserId(user.getId());

        // save user name in order
        orderInfo.setUserName(user.getRealName());

		if(user.getChannel() != null){
			orderInfo.setChannel(user.getChannel());
		}


		// 02添加理财师属性
		if (StringHelper.isNotEmpty(user.getRecommendCode())) {
			SysUser finUser = userService.getByPhoneNum(user.getRecommendCode());
			if (finUser != null && finUser.getIsInside() != null && finUser.getIsInside() == 1) {
				orderInfo.setFinancialPlannerId(finUser.getId());
//				if (finUser.getOrgId() != null) {
//					orderInfo.setOrgId(finUser.getOrgId());
//				}
			}
		}

		if(user.getOrgId() != null){
			orderInfo.setOrgId(user.getOrgId());
		}



		// 03添加产品的信息
		orderInfo.setProductId(prod.getId());
		orderInfo.setCompanyId(prod.getIssuerId());
		orderInfo.setCreditorPhoneNum(prod.getCreditorPhoneNum());
	}
	
	/**
	 * 更新订单的付款信息，收益信息和回款信息
	 * @param orderInfo
	 * @param prod
	 * @param userCardMsg
	 * @param amount
	 */
	public void initOrderMoneyInfo(OrderInfo orderInfo, ProductInfo prod,
			UserCardMsg userCardMsg, BigDecimal amount) {
		
		if(userCardMsg != null){
			orderInfo.setUserCardId(userCardMsg.getUserCardId());
			
			orderInfo.setBenefitType(userCardMsg.getCardType());
		}
		
		//更新订单的支付信息
		initOrderPayInfo(orderInfo, prod, userCardMsg, amount);
		
		//更新订单的收益信息
		initOrderDivInfo(orderInfo, prod, userCardMsg);  
		
		//更新订单的回款信息
		initOrderPayBackInfo(orderInfo, prod, userCardMsg);
		
		
	}
	
	/**
	 * 更新订单中与时间相关的属性
	 * @param orderInfo
	 * @param prod
	 */
	public void initOrderDateInfo(OrderInfo orderInfo, ProductInfo prod) {
		try {
			//订单投资期限
			orderInfo.setTerm(prod.getProTerm());

			// 如果是非自动起息,并且未开始计息
			if (prod.getAutStartDiv() == ConstantProduct.PRO_NO_AUTO_START_DIV
					&& (prod.getStartDiv() == ConstantProduct.PRO_NOT_START_DIV)) {
				orderInfo.setOrderTradeDate(null);
				orderInfo.setDividendDate(null);
			}
			// 如果是自动起息，则添加订单确认日，订单起息日，还本付息日
			if (prod.getAutStartDiv() == ConstantProduct.PRO_AUTO_START_DIV
					|| (prod.getAutStartDiv() == ConstantProduct.PRO_NO_AUTO_START_DIV && (prod
							.getStartDiv() == ConstantProduct.PRO_START_DIV))) {
				Map<String, Long> map = productService.getOrderDate(prod);
				Long conTradeDate = (Long) map.get("startTimeLong");
				Long diviDendDate = (Long) map.get("endTimeLong");
				// 订单确认日:付款之后再确定
				// 交易日T+1
				orderInfo.setOrderTradeDate(conTradeDate);
				// 还本付息
				orderInfo.setDividendDate(diviDendDate);
			}
		} catch (Exception e) {
			logger.error("error:", e);
		}
		logger.info("结束");
	}

	@Override
	public OrderInfo getOrderFromRedis(String key) {
		logger.info("key in the redis is = " + key);

		OrderInfo orderInfo = null;

		// 从缓存中获取订单信息
		if (RedisCilent.existsKey(key)) {

			String orderInfoStr = RedisCilent.getString(key);

			orderInfo = JsonUtils.toBean(orderInfoStr, OrderInfo.class);
			System.out.println("orderInfo = " + orderInfo);
		}

		return orderInfo;
	}

	@Override
	public void delOrderFromRedis(String key) {
		if (RedisCilent.existsKey(key)) {
			RedisCilent.delKey(key);
		}

	}

	@Override
	public OrderInfo updateAndSaveOrder(OrderInfo orderInfo, Integer payStatus,
			Integer confirmStatus) {
		logger.info(
				"PreAuthCtrl  updateOrderStatus orderId={}, userCardId={},  payStatus={}, confirmStatus={}",
				orderInfo.getId(), orderInfo.getUserCardId(), payStatus, confirmStatus);

		orderInfo.setPayStatus(payStatus);
		orderInfo.setConfirmStatus(confirmStatus);

		Long productId = orderInfo.getProductId();
		
		Long userCardId = orderInfo.getUserCardId();
		
		if (confirmStatus == ConstantOrderStatus.CONFIRM_STATUS__TRUE) {
			orderInfo.setOrderConfirmDate(System.currentTimeMillis());
		}

		if (payStatus == ConstantOrderStatus.PAY_STATUS_TRUE) {
			// 支付成功则更改产品的已募集额度
			BigDecimal amount = orderInfo.getSuccessAmount();
			
			userCardService.updateStatus(userCardId, orderInfo.getId(), true);
			
			productService.updAmountByPay(productId, amount, true);
			
			orderRouteService.addByOrder(orderInfo);
		} else {
			// 支付失败则退换加息券
			userCardService.updateStatus(userCardId, orderInfo.getId(), false);
		}

		return orderInfo;

	}

	@Override
	public List<OrderInfo> findPayBackOrders(int confirmStatus, int payStatus,
			Long paymentId) {
		// 当时最大时间
		Long maxTimeLong = DateUtil.endOfTodDay();
		HqlFilter hqlFilter = new HqlFilter();
		hqlFilter.addEQFilter("confirmStatus",
				ConstantOrderStatus.CONFIRM_STATUS__TRUE);
		hqlFilter.addEQFilter("payStatus", ConstantOrderStatus.PAY_STATUS_TRUE);
		hqlFilter.addEQFilter("paymentId", paymentId);

		hqlFilter.addSql(" and dividendDate is not null and dividendDate <  "
				+ maxTimeLong);
		List<OrderInfo> orderList = this.findByFilter(hqlFilter);
		return orderList;
	}

	@Override
	public List<OrderInfo> getProdNewStartOrders() {

		HqlFilter hqlFilter = new HqlFilter();
		hqlFilter.addEQFilter("confirmStatus",
				ConstantOrderStatus.CONFIRM_STATUS__NO_CONFIRM);

		hqlFilter.addEQFilter("payStatus", ConstantOrderStatus.PAY_STATUS_TRUE);

		hqlFilter
				.addSql("  and paymentId = " + ConstantPayment.FYJZH_PAY + " and  productId in ( select p.id from ProductInfo p where p.autStartDiv = 1 or ( p.autStartDiv = 0 and p.startDiv = 1 ))");

		logger.info(" 获取新的起标订单筛选条件是 getProdNewStartOrders  hqlFilter = "
				+ hqlFilter.getWhereAndOrderHql());

		List<OrderInfo> orderList = this.findByFilter(hqlFilter);

		logger.info("orderList size = {}",  orderList!=null?orderList.size():0);

		List<OrderInfo> orderListReturn = null;

		if (orderList != null && orderList.size() > 0) {
			orderListReturn = new ArrayList<OrderInfo>();

			for (OrderInfo order : orderList) {
				Long productId = order.getProductId();
				ProductInfo productInfo = productService.findById(productId);
				Map<String, Long> map = productService
						.getOrderDate(productInfo);
				Long conTradeDate = (Long) map.get("startTimeLong");
				Long diviDendDate = (Long) map.get("endTimeLong");
				// 订单确认日:付款之后再确定
				// 交易日T+1
				order.setOrderTradeDate(conTradeDate);
				// 还本付息
				order.setDividendDate(diviDendDate);

				orderListReturn.add(order);
			}
		}

		logger.info("orderListReturn size = "
				+ (orderListReturn != null ? orderListReturn.size() : 0));

		return orderListReturn;
	}

	@Override
	public void addTransferOrderIntoRedis(Long orderId, String contractNo, String outAccount,
			String inAccount, BigDecimal amt){
		
		TransferOrderMsg transferOrderMsg = new TransferOrderMsg();
		
		transferOrderMsg.setOrderId(orderId);
		transferOrderMsg.setContractNo(contractNo);
		transferOrderMsg.setOutAccount(outAccount);
		transferOrderMsg.setInAccount(inAccount);
		transferOrderMsg.setAmt(amt);
		transferOrderMsg.setStatus(ConstantFYJZH.FYJZH_TRANSFER_STATUS_WAITE);
		transferOrderMsg.setCts(new Timestamp(System.currentTimeMillis()));
		
		logger.info("新增待划拨的订单 :" + transferOrderMsg.toString());
		
		RedisCilent.listSet(ConstantFYJZH.FYJZH_TRANSFER_ORDER_LIST,
				JsonUtils.toJson(transferOrderMsg));
		
	}
	
	@Override
	public void addPaybackOrderIntoRedis(Long orderId, String outAccount, String inAccount, BigDecimal amt){
		
		PaybackOrderMsg paybackOrderMsg = new PaybackOrderMsg();
		
		paybackOrderMsg.setOrderId(orderId);
		paybackOrderMsg.setOutAccount(outAccount);
		paybackOrderMsg.setInAccount(inAccount);
		paybackOrderMsg.setAmt(amt);
		paybackOrderMsg.setStatus(ConstantFYJZH.FYJZH_PACKBACK_STATUS_WAITE);
		paybackOrderMsg.setCts(new Timestamp(System.currentTimeMillis()));
		
		logger.info("新增待回款的订单 :" + paybackOrderMsg.toString());
		
		RedisCilent.listSet(ConstantFYJZH.FYJZH_PAYBACK_ORDER_LIST,
				JsonUtils.toJson(paybackOrderMsg));
		
	}

	 
	
	 

	@Override
	public Boolean startPayBack(Long productId) {
		logger.info("startPayBack 订单回款 productId={}", productId);
		
		Boolean result = true;
		
		HqlFilter hqlfilter = new HqlFilter();
		hqlfilter.addEQFilter("productId", productId);
		hqlfilter.addEQFilter("payStatus", ConstantOrderStatus.PAY_STATUS_TRUE);
		hqlfilter.addEQFilter("confirmStatus", ConstantOrderStatus.CONFIRM_STATUS__TRUE);

		List<OrderInfo> orderList = findByFilter(hqlfilter);
		if(orderList != null) {
			logger.info("startPayBack 产品回款， 回款订单总数 size ={}", orderList.size());
		}
		if (orderList != null && orderList.size() > 0) {
			for (OrderInfo order : orderList) {
			 
				Long orderId = order.getId();
				Long paymentId = order.getPaymentId();


				//回款划拨，清除用户投资资产缓存
				try{
					userCacheService.removeUserAssetCache(order.getUserId());
				}catch (Exception e){
					logger.info("回款划拨，删除用户投资资产缓存错误 error={}", e);
				}


				//如果不是金账户的订单，则直接改确认状态
				if(paymentId.equals(FYJZH_PAYMENT_ID)){
					logger.info("startPayBack 金账户订单回款 orderId ={}", order.getId());
					
					SysUser user = userService.findById(order.getUserId());
					
					//this.addPaybackOrderIntoRedis(orderId, order.getCreditorPhoneNum(), user.getName(), order.getSuccessAmount().add(order.getDividend()) );
					
					logger.info("will start pay back out={},in={}, amount={}", order.getCreditorPhoneNum(), user.getName(), order.getPayBackAmt());
					
					this.addPaybackOrderIntoRedis(orderId, order.getCreditorPhoneNum(), user.getName(), order.getPayBackAmt() );
					
				}else{
					order.setConfirmStatus(ConstantOrderStatus.CONFIRM_STATUS__PAYBACK);
					order.setPayStatus(ConstantOrderStatus.PAY_STATUS_PAYBACK);
				}
				
				this.update(order);
			}

		}

		result = true;

		return result;
	}
	
	public void initOrderPayInfo(OrderInfo orderInfo, ProductInfo prod,
			UserCardMsg userCardMsg, BigDecimal amount) {
		
		// 用户真正支付的金额
		orderInfo.setRealPayAmt(amount.setScale(2, BigDecimal.ROUND_HALF_UP));
		
		BigDecimal benefitAmt = BigDecimal.valueOf(0.00);
		
		if(userCardMsg != null){
			int cardType = userCardMsg.getCardType();
			if( cardType == ConstantCard.CARD_TYPE_TYJ){
				//体验金
				benefitAmt = userCardMsg.getFaceValue();
			} 
		}
		BigDecimal succAmt = amount.add(benefitAmt);
		
		orderInfo.setBenefitAmt(benefitAmt.setScale(2, BigDecimal.ROUND_HALF_UP));
		orderInfo.setSuccessAmount(succAmt.setScale(2, BigDecimal.ROUND_HALF_UP));
		
		if(userCardMsg != null){
			logger.info("initOrderPayInfo: orderId={}, userCardId={}, cardId={}, userCardType={}, realPayAmt={}, benefitAmt={}, succAmt={}", 
				orderInfo.getId(), userCardMsg.getUserCardId(), userCardMsg.getCardId(), amount, benefitAmt, succAmt);
		}else{
			logger.info("initOrderPayInfo: orderId={}", orderInfo.getId());
		}
	 
	
	}
	
	public void initOrderDivInfo(OrderInfo orderInfo, ProductInfo prod,
			UserCardMsg userCardMsg) {

		BigDecimal amount = orderInfo.getSuccessAmount();

		String proRate = prod.getMaxYearRate();
		
		int term = prod.getProTerm();
		
		//产品收益率
		BigDecimal prodRate = DataHelper.chgPrecentToBigDecimal(proRate);
		
		//产品收益
		BigDecimal prodDiv =  DataHelper.getDividend(prodRate, term, amount);

		// 订单设置产品收益率
		orderInfo.setProRate(prodRate);
		logger.info("prodRate ={}", prodRate);

		// 订单设置产品收益
		orderInfo.setProdDividend(prodDiv);
		logger.info("prodDiv ={}", prodDiv);

		//产品平移（增加）收益率
		BigDecimal addRate = productService.getAddRate(prod.getId());
		logger.info("addRate ={}", addRate);
		orderInfo.setProdAddRate(addRate);

		//产品平移（增加）收益
		BigDecimal addRateDiv =  DataHelper.getDividend(addRate, term, amount);
		orderInfo.setAddRateDividend(addRateDiv);
		logger.info("addRateDiv ={}", addRateDiv);

		// 额外收益率 = 加息券收益率 + 额外加息收益率（此时只有额外加息率，优惠券的下面再添加）
		orderInfo.setExtRate(addRate);

		// 额外收益（优惠券收益 +额外加息收益）（此时只有额外加息收益，优惠券的下面再添加）
		orderInfo.setExtraDividend(addRateDiv);

		//总收益率 （产品收益率+额外收益率）
		BigDecimal totalRate = prodRate.add(addRate);

		//总收益 （产品收益 +额外收益）
		BigDecimal totalDividend = DataHelper.getDividend(totalRate, term, amount);

		//设置总收益
		orderInfo.setDividend(totalDividend);

		//设置总收益率
		orderInfo.setTotalRate(totalRate);

		if(userCardMsg != null){
			int cardType = userCardMsg.getCardType();
			switch (cardType){
				case ConstantCard.CARD_TYPE_JXQ: //加息券
					addJXQToOrderInfo(userCardMsg,orderInfo,prod);
				break;
				case ConstantCard.CARD_TYPE_DJQ: //贴息券
					addVoucherToOrderInfo(userCardMsg,orderInfo,prod);
				break;
			}
		}

		logger.info("extRate ={}", orderInfo.getExtRate());
		logger.info("extDiv ={}", orderInfo.getExtraDividend());
		logger.info("totalDividend ={}", orderInfo.getDividend());
		logger.info("totalRate ={}", orderInfo.getTotalRate());
	}

	/**
	 * 添加加息券的订单收益
	 * @param userCardMsg
	 * @param orderInfo
	 * @param productInfo
	 */
	private void addJXQToOrderInfo(UserCardMsg userCardMsg,OrderInfo orderInfo,ProductInfo productInfo){
		int cardDays = userCardMsg.getCardDays();
		BigDecimal cardRate = userCardMsg.getFaceValue();
		BigDecimal cardRateDiv ;
		orderInfo.setUserCardRate(cardRate);
		orderInfo.setUserCardFaceValue(cardRate);
		if(cardDays == 0){
			orderInfo.setExtraTerm(productInfo.getProTerm());
			cardRateDiv = DataHelper.getDividend(cardRate,productInfo.getProTerm(),orderInfo.getRealPayAmt());
		}else{
			orderInfo.setExtraTerm(cardDays);
			cardRateDiv = DataHelper.getDividend(cardRate,cardDays,orderInfo.getRealPayAmt());
		}
		orderInfo.setUserCardDividend(cardRateDiv);
		//更新订单的额外收益和总收益
		BigDecimal extRate = cardRate.add(orderInfo.getExtRate());
		BigDecimal extDividend = cardRateDiv.add(orderInfo.getExtraDividend());
		orderInfo.setExtRate(extRate);
		orderInfo.setExtraDividend(extDividend);

		orderInfo.setTotalRate(cardRate.add(orderInfo.getTotalRate()));
		orderInfo.setDividend(cardRateDiv.add(orderInfo.getDividend()));

	}

	/**
	 * 添加贴息券的订单收益
	 * @param userCardMsg
	 * @param orderInfo
	 * @param productInfo
	 */
	private void addVoucherToOrderInfo(UserCardMsg userCardMsg,OrderInfo orderInfo,ProductInfo productInfo){
		BigDecimal userCardFaceValue = userCardMsg.getFaceValue(); //贴息券是面值100这种类型
		BigDecimal cardRateDiv ;

		//贴息券的收益率 = 面值/购买金额*产品年化收益率
		BigDecimal cardRate = userCardFaceValue.divide(orderInfo.getRealPayAmt()).multiply(orderInfo.getProRate());
		orderInfo.setUserCardRate(cardRate);
		orderInfo.setUserCardFaceValue(userCardFaceValue);
		orderInfo.setExtraTerm(productInfo.getProTerm()); //暂定贴息券的加息天数是产品的期限

		//更新订单的额外收益和总收益
		cardRateDiv = DataHelper.getDividend(orderInfo.getProRate(),productInfo.getProTerm(),userCardFaceValue);
		orderInfo.setUserCardDividend(cardRateDiv);
		BigDecimal extRate = cardRate.add(orderInfo.getExtRate());
		BigDecimal extDividend = cardRateDiv.add(orderInfo.getExtraDividend());
		orderInfo.setExtRate(extRate);
		orderInfo.setExtraDividend(extDividend);

		orderInfo.setTotalRate(cardRate.add(orderInfo.getTotalRate()));
		orderInfo.setDividend(cardRateDiv.add(orderInfo.getDividend()));

	}




	public void initOrderPayBackInfo(OrderInfo orderInfo, ProductInfo prod,
			UserCardMsg userCardMsg) {
		BigDecimal payAmt = orderInfo.getRealPayAmt();
		
		//产品收益
		BigDecimal totalDiv = orderInfo.getDividend();
		
		
		BigDecimal payBackVaul =  payAmt.add(totalDiv);
		
		if(userCardMsg != null && userCardMsg.getCardType() == ConstantCard.CARD_TYPE_TYJ){
			payBackVaul = totalDiv;
		}
		
		orderInfo.setPayBackAmt(payBackVaul.setScale(2, BigDecimal.ROUND_HALF_UP));
		
		
	}

	@Override
	public BigDecimal getTotalPayAmt(Long userId) {
		
		String sql = "SELECT sum(realPayAmt) from t_order_info where userId = " + userId  + " and  (payStatus = 2 or payStatus = 4 ) ";
		 
		BigDecimal totalValue = jdbcTemplate.queryForObject(sql, BigDecimal.class);

		return totalValue == null ? new BigDecimal(0.00) : totalValue;
		 
	}

	@Override
	public BigDecimal getTotalPayAmt(Long userId, Long startTime) {

		String sql = "SELECT sum(realPayAmt) from t_order_info where userId = " + userId  + " and  (payStatus = 2 or payStatus = 4 ) and orderCreatedOn >= " +  startTime;

		BigDecimal totalValue = jdbcTemplate.queryForObject(sql, BigDecimal.class);

		return totalValue == null ? new BigDecimal(0.00) : totalValue;

	}





	@Override
	public String getContractUrl(Long orderId) {
		return null;
	}

	@Override
	public Boolean setContractUrl(Long orderId, String url, String contractTitle) {
		 OrderInfo orderInfo = findById(orderId);
		if(orderInfo != null){
			orderInfo.setContractUrl(url);
			orderInfo.setContractTitle(contractTitle);
		}
		update(orderInfo);
		return true;
	}

	@Override
	public Boolean setContractUrlHtml(Long orderId, String url) {
		OrderInfo orderInfo = findById(orderId);
		if(orderInfo != null){
			orderInfo.setContractUrlHTML(url);
		}
		update(orderInfo);
		return true;
	}

	@Override
	public Boolean check(Long userId, Long productId) {
		Boolean result = true;
		logger.info("check userId={}, productId={}");
		

		if(productId == null || productService.findById(productId) == null){
			return false;
		}

		ProductInfo prod = productService.findById(productId);

		//如果是体验标，检查用户曾经购买了多少
		if(prod.getSaleType() == ConstantProduct.PRODUCT_TEST_PRODUCT){
			HqlFilter hqlfilter = new HqlFilter();
			hqlfilter.addEQFilter("userId", userId);
			hqlfilter.addEQFilter("productId", productId);
			List<OrderInfo> orderList = findByFilter(hqlfilter);
			
			if(orderList != null && orderList.size() > 0){
				result = false;
			}
		}
		
		return result;
	}
	
	private void sendCard(Long userId){
		logger.info("用户下单成功，将检查是否要派送家庭律师卡");
		Parameter parm = parmService.getByName(ConstantParm.SEND_CARD_JTLSK_ID);
		if (parm == null) {
			logger.info("参数配置未查到，停止派送家庭律师卡");
			return;
		}

		if (StringHelper.isEmpty(parm.getValue01()) || StringHelper.isEmpty(parm.getValue02()) || StringHelper.isEmpty(parm.getValue03())) {
			logger.info("参数配置错误，部分参数配置为空，停止派送家庭律师卡! cardId ={}", ConstantParm.SEND_CARD_JTLSK_ID);
			return;
		}

		Long cardId = Long.valueOf(parm.getValue01());
		logger.info("配置的家庭律师卡id={}", cardId);

		Long startTime = DateHelper.stringToDate(parm.getValue02()).getTime();

		logger.info("配置的家庭律师卡 开始时间={}", new Timestamp(startTime));

		BigDecimal limitAmount = new BigDecimal(parm.getValue03());

		logger.info("配置的家庭律师卡 limitAmount={}", limitAmount);

		Long currentTime = System.currentTimeMillis();

		BigDecimal buyAmount =  getTotalPayAmt(userId, startTime);

		logger.info("该用户目前已下单的金额是 buyAmount={}", buyAmount);



		if( currentTime.compareTo(startTime) != -1 && buyAmount.compareTo(limitAmount) != -1) {
			CheckInfo checkInfo = new CheckInfo();
			checkInfo = couponService.sendCoupon(userId, cardId);
			String logRecord = "userId = " + userId +  "   buyAmount = " + buyAmount + "  ------  startTime = " + new Timestamp(startTime) + ", limitAmount = " + limitAmount + ", sendResult = " + checkInfo ;

			writeFile(logRecord);

			logger.info(" 用户下单总金额大于={}， 将赠送家庭律师卡,赠送的结果是={}", limitAmount,  checkInfo);

		}else{
			logger.info("用户下单总金额未大于50000， 将不赠送家庭律师卡", limitAmount);
		}

	}

	public void writeFile(String logRecord) {

		Long cts = System.currentTimeMillis();
		String pathName = "SendJTLSK-"
				+ DateUtil.transferLongToDate("yyyy", cts) + ".txt";


		logger.info("将写入日志文件， logRecord={},pathName={}", logRecord, pathName);

		Path filePath = Paths.get(logsBaseUrl + "/hkLogRecord/" + pathName);



		StringBuffer buffer = new StringBuffer();


		buffer.append(DateUtil.transferLongToDate("yyyy-MM-dd HH:mm:ss", cts) + "----派送家庭律师卡信息:" + logRecord);

		buffer.append("\r\n");
		if (!Files.exists(filePath)) {
			try {
				StringBuilder fileStr = new StringBuilder();
				fileStr.append(buffer);
				// fileStr.append("/n");
				Files.write(filePath, fileStr.toString().getBytes("UTF-8"));
			} catch (IOException e) {
				logger.error("首次写文件失败！", e);
				// e.printStackTrace();
			}
		} else {// 存在则追加
			try {
				Files.write(filePath, buffer.toString().getBytes("UTF-8"),
						StandardOpenOption.APPEND);
			} catch (IOException e) {
				logger.error("追加写文件失败！", e);
				// e.printStackTrace();
			}

		}

	}

    public OrderExcelRes getOrderExcelRes(OrderStrMsg orderStrMsg, Long userId) {
        Boolean isOpear = roleService.isOperationalManager(userId);
        Boolean isChannelLeader = roleService.isDepLeader(userId);
        Boolean isTeamLeader = roleService.isTeamLeader(userId);

		logger.info("isOpear ={}, isChannelLeader={}, isTeamLeader={}", isOpear, isChannelLeader, isTeamLeader );

        return getOrderExcelRes(orderStrMsg, isOpear, isChannelLeader, isTeamLeader);
    }

    public OrderExcelRes getOrderExcelRes(OrderStrMsg orderStrMsg, Boolean isOpear, Boolean isChannelLeader, Boolean isTeamLeader) {
       	logger.info("isOpear ={}, isChannelLeader={}, isTeamLeader={}", isOpear, isChannelLeader, isTeamLeader );
        OrderExcelRes orderExcelRes = new OrderExcelRes();

        //1添加订单直接相关的属性
        orderExcelRes.setCol01id(orderStrMsg.getId());
        orderExcelRes.setCol02amount(orderStrMsg.getAmount());
        orderExcelRes.setCol03niggerAmount(orderStrMsg.getNiggerAmount());
        orderExcelRes.setCol04status(orderStrMsg.getPayStatusStr());
        orderExcelRes.setCol05orderType(orderStrMsg.getOrderType());

        //1* 产品相关信息
        orderExcelRes.setCol10productName(orderStrMsg.getProductName());//产品名称
        orderExcelRes.setCol11productParName(orderStrMsg.getProductParName());//产品父标名称
        orderExcelRes.setCol13productCode(orderStrMsg.getProductCode());//产品code
        orderExcelRes.setCol14productCompanyName(orderStrMsg.getProductCompanyName()) ;//发行公司名称
        orderExcelRes.setCol15productTerm(orderStrMsg.getTerm());//产品投资期限
		orderExcelRes.setCol16clearDate(orderStrMsg.getClearDate()); //预计清算时间
		orderExcelRes.setCol17directional(orderStrMsg.getDirectional()); //是否定向

        //2*订单组织架构相关信息
        orderExcelRes.setCol21userName(orderStrMsg.getUserName());
        orderExcelRes.setCol22userPhoneNum(orderStrMsg.getUserPhoneNum());
        orderExcelRes.setCol23insideName(orderStrMsg.getFinancialPlannerName());
        orderExcelRes.setCol24insidePhoneNum(orderStrMsg.getFinancialPlannerPhoneNum());
        orderExcelRes.setCol25insideDepName(orderStrMsg.getFinancialPlannerDepName());

        orderExcelRes.setCol26channel(orderStrMsg.getChannel());// 订单所属渠道
        orderExcelRes.setCol27channelName(orderStrMsg.getChannelName());// 订单所属的部门全称
        orderExcelRes.setCol28orgName(orderStrMsg.getOrgName());// 订单所属的部门全称
		orderExcelRes.setCol29closeAccount(orderStrMsg.getCloseAccount()==null ? "已销户" : (orderStrMsg.getCloseAccount()==1?"已销户":"末销户")); // 是否销户（0：末销户，1：已销户）

        //3*合同相关附加信息
		List<OrderContract> orderContractList = this.orderContractService.getOrderContractList(Long.valueOf(orderStrMsg.getId()));
		for (int i = 0; i < orderContractList.size(); i++) {
			OrderContract orderContract = orderContractList.get(i);
			switch (i) {
				case 0:
					orderExcelRes.setCol36contractTitle1(orderContract.getContractTitle());
					orderExcelRes.setCol36contractUrlHTML1(QN_PDF + orderContract.getContractHTMLUrl());
					orderExcelRes.setCol36contractUrlPDF1(QN_PDF + orderContract.getContractPDFUrl());
					break;
				case 1:
					orderExcelRes.setCol36contractTitle2(orderContract.getContractTitle());
					orderExcelRes.setCol36contractUrlHTML2(QN_PDF + orderContract.getContractHTMLUrl());
					orderExcelRes.setCol36contractUrlPDF2(QN_PDF + orderContract.getContractPDFUrl());
					break;
				case 2:
					orderExcelRes.setCol36contractTitle3(orderContract.getContractTitle());
					orderExcelRes.setCol36contractUrlHTML3(QN_PDF + orderContract.getContractHTMLUrl());
					orderExcelRes.setCol36contractUrlPDF3(QN_PDF + orderContract.getContractPDFUrl());
					break;
				case 3:
					orderExcelRes.setCol36contractTitle4(orderContract.getContractTitle());
					orderExcelRes.setCol36contractUrlHTML4(QN_PDF + orderContract.getContractHTMLUrl());
					orderExcelRes.setCol36contractUrlPDF4(QN_PDF + orderContract.getContractPDFUrl());
					break;
				case 4:
					orderExcelRes.setCol36contractTitle5(orderContract.getContractTitle());
					orderExcelRes.setCol36contractUrlHTML5(QN_PDF + orderContract.getContractHTMLUrl());
					orderExcelRes.setCol36contractUrlPDF5(QN_PDF + orderContract.getContractPDFUrl());
					break;

			}
		}

		if (orderContractList.size() == 0) {
			orderExcelRes.setCol31contractTitle(orderStrMsg.getContractTitle());//合同标题
			if(StringHelper.isNotEmpty(orderStrMsg.getContractUrl())){
				String url = orderStrMsg.getContractUrl();
				orderExcelRes.setCol32contractUrlPDf(QN_PDF + url);
			}
		}

		orderExcelRes.setCol33confirmationTitle(orderStrMsg.getConfirmationTitle());//投资确认函标

        if(StringHelper.isNotEmpty(orderStrMsg.getContractUrlHTML())){
			String url = orderStrMsg.getContractUrlHTML();
            orderExcelRes.setCol32contractUrlHTML(QN_PDF + url);
        }

        if(StringHelper.isNotEmpty(orderStrMsg.getConfirmationPdf())){
			String url = orderStrMsg.getConfirmationPdf();

            orderExcelRes.setCol34confirmationPdf(QN_PDF + url);
        }
        if(StringHelper.isNotEmpty(orderStrMsg.getConfirmationHtml())){
			String url = orderStrMsg.getConfirmationHtml();
            orderExcelRes.setCol35confirmationHtml(QN_PDF + url);
        }


        //4*收益相关信息
        orderExcelRes.setCol410proRate(orderStrMsg.getProRate()); //产品收益率
        orderExcelRes.setCol412prodDividend(orderStrMsg.getProdDivendend()); //产品收益
        orderExcelRes.setCol420prodAddRate(orderStrMsg.getProdAddRate());//产品额外加息收益率
        orderExcelRes.setCol421addRateDividend(orderStrMsg.getAddRateDividend()); //产品额外加息收益
		if (orderStrMsg.getBenefitType() == ConstantCard.CARD_TYPE_JXQ){
			orderExcelRes.setCol430userCardId(orderStrMsg.getUserCardId());//加息券id
			orderExcelRes.setCol431userCardRate(orderStrMsg.getUserCardRate()); //加息券收益率
			orderExcelRes.setCol432userCardDividend(orderStrMsg.getUserCardDividend()); //加息券收益
		}else if(orderStrMsg.getBenefitType() ==ConstantCard.CARD_TYPE_DJQ){
			orderExcelRes.setCol4301userCardId(orderStrMsg.getUserCardId());//贴息券id
			orderExcelRes.setCol4311userCardRate(orderStrMsg.getUserCardRate()); //贴息券收益率
			orderExcelRes.setCol4321userCardDividend(orderStrMsg.getUserCardDividend()); //贴息券收益
			orderExcelRes.setCol435userCardFaceValue(String.valueOf(orderStrMsg.getUserCardFaceValue()
					==null ?"0":Double.valueOf(orderStrMsg.getUserCardFaceValue()).intValue()));//优惠券面值
		}

        orderExcelRes.setCol433extraTerm(orderStrMsg.getExtraTerm()); //加息券加息天数
        orderExcelRes.setCol480extRate(orderStrMsg.getExtRate()); //其它收益  = userCardRate + prodAddRate
        orderExcelRes.setCol481extraDividend(orderStrMsg.getExtraDivendend());// 其它收益
        orderExcelRes.setCol490totalRate(orderStrMsg.getTotalRate()); //总收益率 = proRate + extRate
        orderExcelRes.setCol491dividend(orderStrMsg.getDividend()); //总收益
		orderExcelRes.setCol434benefitType(String.valueOf(orderStrMsg.getBenefitType())); //订单优惠类型：1,加息券; 2:体验金; 5:贴息券

        //5*订单时间属性
        orderExcelRes.setCol51cts(orderStrMsg.getOrderCreatedOnStr());//订单确认时间
        orderExcelRes.setCol52dividendDate(orderStrMsg.getOrderDividendDateStr());//回款日
        orderExcelRes.setCol53beginProfitDate(orderStrMsg.getOrderTradeDateStr());// 起息时间


        //7*银行卡相关信息
        orderExcelRes.setCol71identity(orderStrMsg.getIdentity());// 银行身份证
        orderExcelRes.setCol72bankName(orderStrMsg.getPaymentBankName());  // 银行信息
        orderExcelRes.setCol73paymentNo(orderStrMsg.getPaymentBankCardNo());// 银行卡号
        orderExcelRes.setCol74subBankName(orderStrMsg.getSubBankName());//分行名称

		if (StringHelper.isNotBlank(orderStrMsg.getKycUrl())) {
			orderExcelRes.setKycUrl(QN_PDF + orderStrMsg.getKycUrl());
		}

		orderExcelRes.setRiskLevel(orderStrMsg.getRiskLevel());

        //处理数据
        if ("4".equals(orderStrMsg.getProductCompanyId())) {
            orderExcelRes.setCol10productName("公募基金-"
                    + orderStrMsg.getProductName());
        }


        //根据不同的角色设置数据权限
        if (isOpear) {
            orderExcelRes.setCol22userPhoneNum(orderStrMsg.getUserPhoneNum());
        } else if(isChannelLeader || isTeamLeader){
            String name = DataUtil.getEncryptRealName(orderStrMsg.getUserName());
            orderExcelRes.setCol21userName(name);
            orderExcelRes.setCol22userPhoneNum(null);
            orderExcelRes.setCol73paymentNo(null);
            orderExcelRes.setCol71identity(null);
            orderExcelRes.setCol72bankName(null);
			orderExcelRes.setCol73paymentNo(null);
			orderExcelRes.setCol74subBankName(null);

            orderExcelRes.setCol32contractUrlPDf(null);
            orderExcelRes.setCol32contractUrlHTML(null);
            orderExcelRes.setCol31contractTitle(null);

			orderExcelRes.setCol36contractTitle1(null);
			orderExcelRes.setCol36contractTitle2(null);
			orderExcelRes.setCol36contractTitle3(null);
			orderExcelRes.setCol36contractTitle4(null);
			orderExcelRes.setCol36contractTitle5(null);

			orderExcelRes.setCol36contractUrlHTML1(null);
			orderExcelRes.setCol36contractUrlHTML2(null);
			orderExcelRes.setCol36contractUrlHTML3(null);
			orderExcelRes.setCol36contractUrlHTML4(null);
			orderExcelRes.setCol36contractUrlHTML5(null);

			orderExcelRes.setCol36contractUrlPDF1(null);
			orderExcelRes.setCol36contractUrlPDF2(null);
			orderExcelRes.setCol36contractUrlPDF3(null);
			orderExcelRes.setCol36contractUrlPDF4(null);
			orderExcelRes.setCol36contractUrlPDF5(null);

			orderExcelRes.setRiskLevel(null);
			orderExcelRes.setKycUrl(null);

            String encrypefinPhone = DataUtil.getEncryptPhoneNum(orderExcelRes.getCol24insidePhoneNum());
            orderExcelRes.setCol24insidePhoneNum(encrypefinPhone);
        }else {
			String userPhone = orderExcelRes.getCol22userPhoneNum();
			String encrypeUserPhone = DataUtil.getEncryptPhoneNum(userPhone);
			orderExcelRes.setCol22userPhoneNum(encrypeUserPhone);
			orderExcelRes.setCol71identity(null);
			orderExcelRes.setCol72bankName(null);
			orderExcelRes.setCol73paymentNo(null);
			orderExcelRes.setCol74subBankName(null);
        }


        return orderExcelRes;
    }


	@Override
	public CheckInfo updOrderFinUserId(SysUser finUser, Long orderId, Long actUserId) {

		CheckInfo checkInfo = new CheckInfo();

		try{

			OrderInfo order = findById(orderId);
			OrderRouteInfo orderRouteInfo = orderRouteService.findByOrderId(orderId);

			LogUtil logRecord = new LogUtil();
			logRecord.setActUserId(actUserId);
			logRecord.setType(ConstantLog.LOG_TYPE_ORDER);
			logRecord.setChgDesc("修改订单推荐码和渠道 orderId : " + order.getId());
			logRecord.setRecordId(order.getId());

			OrderStrMsg orderMsg = orderContent.getOrderInfo(order.getId(), order.getUserId(), order.getCompanyId());
			OrderExcelRes orderExcelRes = getOrderExcelRes(orderMsg, actUserId);

			// 在日志表中保存修改之前的镜像
			String beforeImgStr = JsonUtils.toJson(orderExcelRes);

			logRecord.setBeforeImg(beforeImgStr);

			// 如果理财师不为空
			if (finUser != null) {
				order.setFinancialPlannerId(finUser.getId());

				if (orderRouteInfo != null) {
					orderRouteInfo.setFinancialPlannerId(finUser.getId());
				}

				if (finUser.getOrgId() != null) {
					order.setOrgId(finUser.getOrgId());
					order.setChannel(finUser.getChannel());
				}
			}

			this.update(order);
			orderRouteService.update(orderRouteInfo);

			OrderInfo newOrder = findById(order.getId());

			OrderStrMsg orderNewStrMsg = orderContent.getOrderInfo(order.getId(), order.getUserId(), order.getCompanyId());

			OrderExcelRes newOrderExcelRes = getOrderExcelRes(orderNewStrMsg,  actUserId);
			// 在日志表中保存修改之后的镜像
			String afterImgStr = JsonUtils.toJson(newOrderExcelRes);
			logRecord.setAfterImg(afterImgStr);

			// 加入日志表中
			logService.add(logRecord);

			checkInfo.setResult(true);
			checkInfo.setResultMsg("修改成功");
		} catch (Exception ex) {
			logger.error(ex.getMessage(), ex);
			checkInfo.setResult(false);
			checkInfo.setResultMsg("操作异常，请稍后重试");
		}
		return checkInfo;
	}


	@Override
	public void createOrderKyc(long orderId) {
		OrderInfo orderInfo = this.findById(orderId);
		Answer answer = answerService.getByUserId(orderInfo.getUserId());
		if(answer != null && StringHelper.isNotEmpty(answer.getScoreDesc())){
			orderInfo.setRiskLevel(answer.getScoreDesc());
		}

		//如果用户的kyc 还未生成
		if(StringHelper.isEmpty(answer.getKycHTMLUrl()) || StringHelper.isEmpty(answer.getKycPDFUrl())){
			SysUser user = userService.findById(orderInfo.getUserId());
			if(StringHelper.isNotEmpty(user.getRealName()) && StringHelper.isNotEmpty(user.getIdentity())){
				//用户已经绑卡
				answerService.updKycUrl(orderInfo.getUserId());
			}
		}
		orderInfo.setKycPDFUrl(answer.getKycPDFUrl());
		orderInfo.setKycHTMLUrl(answer.getKycHTMLUrl());
		this.update(orderInfo);
	}

	@Override
	public Long countInTransitOrder(Long userId) {
		HqlFilter hql = new HqlFilter();
		hql.addEQFilter("userId",userId);
		hql.addEQFilter("payStatus",2);
		return countByFilter(hql);
	}

	/**
	 * 渠道 分公司过滤
	 * @param channel 渠道
	 * @param orgId 分公司
	 * @param hqlFilter
	 * @return
	 */
	@Override
	public boolean getCustomFieldForOrderInfo(Integer channel, String orgId, HqlFilter hqlFilter) {
		logger.info("-------------->channel{}, orgId{}", channel, orgId );
		if(channel != null && !StringUtils.isBlank(orgId)) {
			String orderCodeSql = "select ord.id as ordId from t_order_info ord,t_organization org where ord.orgId is not null and ord.channel = "+channel+" and org.`code` LIKE '"+orgId+"%' and ord.orgId = org.id ";
			String orderCodeStr = getChannel(orderCodeSql);

			if(!StringUtils.isBlank(orderCodeStr)) {
				hqlFilter.addSql(" and orderId in ( " + orderCodeStr+ " )");
			}else{
				hqlFilter.addSql(" and orderId not in ( select id from OrderInfo ) ");
				return true;
			}
		}else if(channel != null){
			String channelSql = "select id from t_order_info where channel = " + channel;
			String channelStr = getChannel(channelSql);
			if(!StringUtils.isBlank(channelStr)) {
				hqlFilter.addSql(" and orderId in ( " + channelStr+ " )");
			}else {
				hqlFilter.addSql(" and orderId not in ( select id from OrderInfo ) ");
				return true;
			}
		}
		return false;
	}

	/**
	 * 通过渠道channelId查找旗下分公司
	 * @param channelId
	 * @return
	 */
	@Override
	public List<OrganizationFiled> getOrgList(String channelId) {
		List<OrganizationFiled> list = new ArrayList<>();
		if(StringUtils.isNotBlank(channelId)) {

			String sql = "SELECT code, flag02 from t_organization where flag01 = 1 and orgType = 3 and channel = " + channelId;
			jdbcTemplate.query(sql,
					new RowMapper(){
						@Override
						public Object mapRow(ResultSet rs, int rowNum)throws SQLException {
							OrganizationFiled organizationDTO  = new OrganizationFiled();
							organizationDTO.setOrgId(rs.getString("code"));
							organizationDTO.setOrgName(rs.getString("flag02"));
							list.add(organizationDTO);
							return list;
						}
					}
			);
		}

		return list;
	}

	/**
	 * 获取用户渠道
	 * @param userId
	 * @return
	 */
	@Override
	public List<UserChannel> getUserList(String userId) {
		if(StringUtils.isBlank(userId)) {
			new Exception("获取用户渠道的 userId 为空");
		}

		HqlFilter hqlFilter = new HqlFilter();
		SysUser user = userService.findById(Long.valueOf(userId));
		Boolean isOpear = roleService.isOperationalManager(user.getId());

		// 如果不是运营部的人员，则添加筛选条件
		if (!isOpear) {
			// 增加组织架构的筛选
			if (user.getOrgId() != null) {
				Organization org = orgService.findById(user.getOrgId());

				//如果用户是部门负责人
				if(roleService.isDepLeader(Long.valueOf(userId)) ){
					logger.info("user is leader, userId ={}", userId);

					String appendSql = " where channelId in ( -1, ";
					List<Integer > channelIdList  = orgNewService.getDepLeaderChannelStrList(Long.valueOf(userId));
					appendSql += StringUtils.join(channelIdList, ",") + ")";

					hqlFilter.addSql(appendSql);
				}else if (org != null && org.getIsHeader() == 1 && roleService.isTeamLeader(Long.valueOf(userId))) {
					//如果是某个团队的负责人
					String code = orgService.getOrgLeaderCodeByOrgId(org.getId());
					String[] split = code.split("-");
					String appendSql = " where channelId =" + split[2];
					hqlFilter.addSql(appendSql);

				}
			}
		}
		List<UserChannel> result = userChannelService.findByFilter(hqlFilter);

		return result;
	}

	/**
	 * 获取渠道
	 * @param channelSql
	 * @return
	 */
	private String getChannel(String channelSql) {
		List<Long> idsList = jdbcTemplate.queryForList(channelSql, Long.class);
		String userIds = null;
		String join = StringUtils.join(idsList, ",");
		userIds = join;
		return userIds;
	}
}
